package com.gaiso.gaisopush.push;

import com.gaiso.gaisopush.data.PushConstant;

import org.eclipse.paho.client.mqttv3.IMqttMessageListener;
import org.eclipse.paho.client.mqttv3.MqttClient;
import org.eclipse.paho.client.mqttv3.MqttConnectOptions;
import org.eclipse.paho.client.mqttv3.MqttException;
import org.eclipse.paho.client.mqttv3.MqttMessage;
import org.eclipse.paho.client.mqttv3.persist.MemoryPersistence;

/**
 * Created by WangDongJie on 2017/4/20.
 */

public class PushCore implements IPushCore {

    private static final String KEEP_ALIVE = "keep_alive";
    private static final int QOS = 2;
    private MqttClient mClient;
    private IPushCallback mCallback;
    private MqttConnectOptions mConnectOpt = new MqttConnectOptions();

    private PushCore() {
        mConnectOpt.setCleanSession(true);
    }

    public static PushCore getInstance() {
        return SingletonHolder.INSTANCE;
    }

    private static class SingletonHolder {
        private static final PushCore INSTANCE = new PushCore();
    }

    @Override
    public void connect(String clientId, String broker) throws MqttException {
        MemoryPersistence persistence = new MemoryPersistence();
        mClient = new MqttClient(broker, clientId, persistence);
        mClient.connect(mConnectOpt);
        subscribe(PushConstant.GAISO_PUSH_TOPIC);
    }

    @Override
    public boolean isConnected() {
        return mClient != null && mClient.isConnected();
    }

    @Override
    public void disconnect() throws MqttException {
        mClient.disconnect();
    }

    @Override
    public void close() throws Exception {
        mClient.close();
    }

    @Override
    public void keepAlive() throws MqttException {
        MqttMessage msg = new MqttMessage(KEEP_ALIVE.getBytes());
        msg.setQos(QOS);
        String topic = mClient.getClientId() + ":" + KEEP_ALIVE;
        mClient.publish(topic, msg);
    }

    @Override
    public void publish(String topic, MqttMessage message) throws MqttException {
        mClient.publish(topic, message);
    }

    @Override
    public void subscribe(String topic) throws MqttException {
        if (mCallback != null)
            mClient.subscribe(topic, new IMqttMessageListener() {
                @Override
                public void messageArrived(String topic, MqttMessage message) throws Exception {
                    mCallback.messageArrived(topic, message.getPayload());
                }
            });
        else
            mClient.subscribe(topic);
    }

    @Override
    public void unSubscribe(String topic) throws MqttException {
        mClient.unsubscribe(topic);
    }

    @Override
    public void setCallback(IPushCallback callback) {
        if (mCallback == null) mCallback = callback;
    }
}
